package com.qst.order.controller;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.qst.order.domain.DTO.*;
import com.qst.order.domain.Merchant;
import com.qst.order.domain.Order;
import com.qst.order.domain.OrderItem;
import com.qst.order.domain.User;
import com.qst.order.service.OrderItemService;
import com.qst.order.service.OrderService;
import com.qst.order.service.ReplenishRecordService;
import com.qst.order.service.UserService;
import com.qst.order.utils.JwtUtil;
import com.qst.order.utils.Result;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping("/api/merchant")
@Slf4j
@RequiredArgsConstructor
public class MerchantController {

    private final JwtUtil jwtUtil;
    private final OrderService orderService;
    private final OrderItemService orderItemService;
    private final UserService userService;
    private final PasswordEncoder passwordEncoder;
    private final ReplenishRecordService replenishRecordService;
    @GetMapping("/status")
    public Result<IPage<OrderItem>> getMerchantOrderItemsByStatus(
            @RequestParam(defaultValue = "1") Integer pageNum,
            @RequestParam(defaultValue = "10") Integer pageSize,
            @RequestHeader("Authorization")String token,
            @RequestParam(required = false) String status,
            @RequestParam(required = false) String startDate,
            @RequestParam(required = false) String endDate,
            @RequestParam(required = false) String sortType,
            @RequestParam(required = false) String searchKey) {

        // 构建分页对象
        IPage<OrderItem> page = new Page<>(pageNum, pageSize);
        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        // 调用服务层方法，传递所有筛选参数
        IPage<OrderItem> byMerchantIdAndStatusWithRelations = null;
        try {
            byMerchantIdAndStatusWithRelations = orderService.getByMerchantIdAndStatusWithRelations(
                    page,
                    merchantId,
                    status,
                    startDate,
                    endDate,
                    sortType,
                    searchKey
            );
        } catch (Exception e) {
            log.error("获取商家订单项失败：{}", e.getMessage());
            throw new RuntimeException(e);
        }

        return Result.success(byMerchantIdAndStatusWithRelations);
    }

    //加载商家信息
    @GetMapping("/profile/shop")
    public Result getMerchantProfile(@RequestHeader("Authorization") String token) {
        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        return Result.success(userService.getMerchantProfile(merchantId));
    }
    @PutMapping("/profile/shop")//修改商家信息
    public Result UpdateMerchantProfile(@RequestHeader("Authorization") String token,@RequestBody Merchant merchant) {
        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        try {
            userService.updateMerchantProfile(merchant,merchantId);
        } catch (Exception e) {
            log.warn("更新商家信息失败:{}",e);
            throw new RuntimeException(e);
        }
        return Result.success();
    }


    @GetMapping("/statistics/order-items")
    public Result<List<OrderItemDTO>> getMerchantOrderItemsStatistics(
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate startDate,
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  endDate,
            // 从当前登录用户中获取商家ID（示例）
            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        List<OrderItemDTO> list = orderItemService.getOrderItemList(startDate, endDate, merchantId);
        return Result .success(list);
    }


    @PutMapping("/security/password")
    public Result updatePassword(@RequestHeader("Authorization") String token, @Valid @RequestBody UpdatePasswordDTO updatePasswordDTO) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        User user = userService.getById(merchantId);
        if (!passwordEncoder.matches(updatePasswordDTO.getOldPassword(), user.getPassword())){
            return Result.error("旧密码错误");
        }
         userService.lambdaUpdate().eq(User::getId, merchantId)
                .set(User::getPassword, passwordEncoder.encode(updatePasswordDTO.getNewPassword())).update();
        return Result.success();
    }

    @GetMapping("/statistics/overview")
    public Result getMerchantOverviewStatistics(
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  startDate,
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  endDate,
            // 从当前登录用户中获取商家ID（示例）
            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        OverviewDTO overview = null;
        try {
            overview = orderItemService.getOverview(startDate, endDate, merchantId);
        } catch (Exception e) {
            log.warn("获取商家订单统计失败:{}",e);
            throw new RuntimeException(e);
        }
        return Result.success(overview);
    }
    @GetMapping("/statistics/trend")
    public Result getMerchantTrendStatistics(
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  startDate,
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  endDate,
            // 从当前登录用户中获取商家ID（示例）
            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        TrendDTO trend = null;
        try {
            trend = orderItemService.getTrend(startDate, endDate, merchantId);
        } catch (Exception e) {
            log.warn("获取商家订单统计失败:{}",e);
            throw new RuntimeException(e);
        }

        return Result.success(trend);


    }

    @GetMapping("/statistics/order-status")
    public Result getMerchantOrderStatusStatistics(
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  startDate,
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  endDate,
            // 从当前登录用户中获取商家ID（示例）
            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        try {
            return Result.success(orderItemService.getOrderStatusDistribution(startDate, endDate, merchantId));
        } catch (Exception e) {
            log.warn("订单状态报错:{}",e);
            throw new RuntimeException(e);
        }
    }
    @GetMapping("/statistics/top-products")
    public Result getMerchantTopProductsStatistics(
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  startDate,
            @RequestParam @DateTimeFormat(pattern = "yyyy-MM-dd") LocalDate  endDate,
            // 从当前登录用户中获取商家ID（示例）
            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));

        try {
            List<TopProductDTO> topProducts = orderItemService.getTopProducts(startDate, endDate, merchantId, 5);
            return Result.success(topProducts);
        } catch (Exception e) {
            log.warn("获取商家商品统计失败:{}",e);
            throw new RuntimeException(e);
        }


    }
    @PostMapping("/orders/{orderId}/ship")//发货
    public Result shipOrder(
            @PathVariable("orderId") Integer orderId, @RequestBody OrderShipDTO orderShipDTO) {
        log.warn("信息：{}",orderShipDTO);
        orderService.lambdaUpdate()
                .eq(Order::getOrderId, orderId)
                .set(Order::getStatus, "shipped")
                .set(Order::getShippingTime, LocalDateTime.now())
                .update();
        orderItemService.lambdaUpdate().set(OrderItem::getItemStatus, "shipped")
                .set(OrderItem::getLogisticsNo, orderShipDTO.getLogisticsNo())
                .set(OrderItem::getLogisticsCompany, orderShipDTO.getLogisticsCompany())
                .set(OrderItem::getRemark, orderShipDTO.getRemark())
                .set(OrderItem::getShipTime,LocalDateTime.now())
                .in(OrderItem::getItemId,orderShipDTO.getOrderItemIds()).update();
        return Result.success("发货成功");
    }

    @PostMapping("/orders/batch-ship")
    @Transactional
    public Result batchShipOrders(@RequestBody BatchShipDTO batchShipDTO) {
        log.warn("批量发货信息：{}", batchShipDTO);

        // 验证参数：订单项ID数量需与物流单号数量一致（核心！）
        if (batchShipDTO.getOrderItemIds() == null || batchShipDTO.getLogisticsNoList() == null ||
                batchShipDTO.getOrderItemIds().size() != batchShipDTO.getLogisticsNoList().size()) {
            return Result.error("订单项ID数量与物流单号数量不匹配");
        }

        int successCount = 0;
        int failCount = 0;

        // 循环处理每个订单项（一对一更新）
        for (int i = 0; i < batchShipDTO.getOrderItemIds().size(); i++) {
            Integer itemId = batchShipDTO.getOrderItemIds().get(i); // 单个订单项ID
            String logisticsNo = batchShipDTO.getLogisticsNoList().get(i); // 对应的单个物流单号

            try {
                // 1. 更新订单项状态（单个订单项）
                orderItemService.lambdaUpdate()
                        .set(OrderItem::getItemStatus, "shipped")
                        .set(OrderItem::getLogisticsNo, logisticsNo) // 传入单个单号（关键修正）
                        .set(OrderItem::getLogisticsCompany, batchShipDTO.getLogisticsCompany())
                        .set(OrderItem::getRemark, batchShipDTO.getRemark())
                        .set(OrderItem::getShipTime, LocalDateTime.now())
                        .eq(OrderItem::getItemId, itemId) // 精确更新当前订单项
                        .update();

                // 2. （可选）如果需要更新订单状态，先查询该订单项所属的订单ID
                OrderItem item = orderItemService.getById(itemId);
                if (item != null) {
                    Integer orderId = item.getOrderId();
                    // 检查该订单下所有订单项是否都已发货，再更新订单状态（避免部分发货时误更新）
                    long unshippedCount = orderItemService.lambdaQuery()
                            .eq(OrderItem::getOrderId, orderId)
                            .ne(OrderItem::getItemStatus, "shipped")
                            .count();
                    if (unshippedCount == 0) { // 所有订单项都已发货
                        orderService.lambdaUpdate()
                                .eq(Order::getOrderId, orderId)
                                .set(Order::getStatus, "shipped")
                                .set(Order::getShippingTime, LocalDateTime.now())
                                .update();
                    }
                }

                successCount++;
            } catch (Exception e) {
                log.error("订单项{}发货失败", itemId, e);
                failCount++;
            }
        }

        return Result.success("批量发货处理完成", Map.of("successCount", successCount, "failCount", failCount));
    }


    /**
     * 单个商品补货
     */

    @PostMapping("/products/{productId}/replenish")
    public Result<?> replenishProduct(
            @PathVariable("productId") Integer productId,
            @RequestBody @Valid SingleReplenishDTO replenishDTO,
            @RequestHeader(value = "Authorization") String token
    ) {
        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        String  operateUserName = jwtUtil.getClaim(token, "username");
        try {
            replenishRecordService.createSingleRecord(productId, replenishDTO.getQuantity(), replenishDTO.getReason(),
                    replenishDTO.getRemark(), merchantId, operateUserName);
        } catch (Exception e) {
            log.warn("商品补货报错:{}",e);
            throw new RuntimeException(e);
        }
        return Result.success("商品补货成功");
    }

    /**
     * 批量商品补货
     */
    @PostMapping("/products/batch-replenish")
    public Result<?> batchReplenishProducts(@Validated @RequestBody ReplenishRequest request,
                                            @RequestHeader("Authorization") String token) {

        Integer merchantId = Integer.valueOf(jwtUtil.getClaim(token, "userId"));
        String operateUserName = jwtUtil.getClaim(token, "username");
        try {
            replenishRecordService.batchCreateRecord(request.getProductIds(), request.getQuantity(), request.getReason(), request.getMethod(),
                    request.getRemark(), merchantId, operateUserName);
        } catch (Exception e) {
            log.warn("商品批量补货报错:{}",e);
            throw new RuntimeException(e);
        }

        return Result.success("商品补货成功");
    }





}
